<?php

namespace app\backend\controller;

use app\backend\model\AuthNode;
use app\backend\model\Auth;
use think\Controller;

/**
 * 基础类
 * @author Ray 541720500@qq.com
 */
class Base extends Controller
{
    protected $beforeActionList = [
        'checkAuth' => ['except' => 'loginform,login,logout'], // 不支持驼峰写法
    ];

    public function handleValidate($data, $type = null)
    {
        $conf = config("validate.");
        $result = $this->validate($data, $conf[$type], isset($conf[$type . '_msg']) ? $conf[$type . '_msg'] : null);
        if (true !== $result)
            $this->error($result);
    }

    public function initialize()
    {
        if (cache('system_menu')) {
            $menu = cache('system_menu');
        } else {
            $menu = AuthNode::getMenus();
        }

        // 获取面包屑路径：
        $cur_url = request()->controller() . '/' . request()->action();
        $act_title = '';
        $ctr_title = '';
        foreach ($menu as $v) {
            if (strtolower($v['url']) == strtolower($cur_url)) {
                $ctr_id = $v['parent_id'];
                $act_title = $v['title'];
            }
        }
        if ($act_title && isset($ctr_id) && $ctr_id != 0) {
            foreach ($menu as $v) {
                if ($v['id'] == $ctr_id) {
                    $ctr_title = $v['title'];
                }
            }
        }
        $this->assign([
            'ctr_title' => $ctr_title,
            'act_title' => $act_title
        ]);
    }

    // 执行创建方法
    public function handleCreate($input = null)
    {
        if ($input == null) {
            $input = input('post.');
        }
        if (input('_m') == null) {
            $this->error('缺少设置模型');
        }
        $this->modelCreate(input('_m'), $input, input('_vali', ''), input('_title'));
    }

    // 执行修改方法
    public function handleSave($input = null)
    {
        if ($input == null) {
            $input = input('post.');
        }
        if (input('_m') == null) {
            $this->error('缺少设置模型');
        }
        if (input('id') == null) {
            $this->error('缺少修改条件');
        }
        $this->modelUpdate(input('_m'), $input, ['id' => input('id')], input('_vali', ''), input('_remark'), input('_cb'));
    }

    // 执行删除方法
    public function handleDel()
    {
        if (input('_m') == null) {
            $this->error('缺少删除模型');
        }
        if (input('id') == null) {
            $this->error('缺少删除条件');
        }
        return $this->modelDelete(input('_m'), ['id' => input('id')]);
    }

    protected function checkAuth()
    {
        // 检查session
        $admin_id = session('adm_id');
        $admin_name = session('account');
        if ($admin_id == false)
            $this->error('请登录', 'login/loginForm');

        // 判断是否为超级管理员
        $super_admins = explode(',', config('status.auth.super_auth_adm'));
        if (in_array($admin_name, $super_admins) === true)
            return true; // 超级管理员跳过验证

        // 获取当前控制器的id
        $controller = strtolower(request()->controller());
        $action = strtolower(request()->action());

        $no_auth_controller = explode(',', strtolower(config('status.auth.no_auth_controller')));
        if (in_array($controller, $no_auth_controller))
            return true;

        // 获取当前用户的节点列表
        $auth_nodes = Auth::getAuthNodes($admin_id);
        if ($auth_nodes == 'norole') {
            $this->error('该账号还未设置管理组！');
        } elseif ($auth_nodes == 'nonode') {
            $this->error('该账号还未设置权限！');
        }

        // 判断controller是否在许可范围内
        $ctrl_id = AuthNode::where('name', $controller)->cache(true)->value('id');
        if (in_array($ctrl_id, $auth_nodes) === false)
            $this->error('您没有权限访问！');

        // 判断action是否在许可范围内
        $act_id = AuthNode::where(['name' => $action, 'parent_id' => $ctrl_id])->cache(true)->value('id');
        if (in_array($act_id, $auth_nodes) === false)
            $this->error('您没有权限访问该页！');

        return true;
    }

    // 管理员日志
    protected function makeLog($content)
    {
        $data['add_time'] = now();
        $data['adm_id'] = session('adm_id');
        $data['adm_account'] = session('account');
        $data['ip'] = request()->ip();
        $data['path'] = request()->path();
        $data['content'] = $content;
        $result = db('adm_log')->insert($data);
        if ($result == false) \think\Log::record('管理员日志写入错误');
    }

    /*
    * name：dbAdd数据删除方法
    * param：数据库，数据
    */
    protected function dbAdd($db, $data, $path = "", $word = "添加")
    {
        $res = db($db)->insert($data);
        if ($res) $this->makeLog('[新增成功] [DB] ' . $db);
        $res ? $this->success($word . '成功', $path) : $this->error($word . '失败', $path);
    }

    protected function modelUpdate($model, $data, $condition = [], $validate = '', $msg = '修改', $callback = null)
    {
        if ($validate) {
            $this->handleValidate($data, $validate);
        }
        $res = model($model)->allowField(true)->save($data, $condition);
        if (false === $res) {
            $this->error(model($model)->getError());
        } elseif ($res === 0) {
            $this->error('无' . $msg);
        } elseif ($res) {
            $this->makeLog("[" . $msg . "成功] [MODEL] " . $model);
            if ($callback) {
                if (is_callable($callback)) {
                    $callback($condition);

                } elseif (is_string($callback)) {
                    action($callback, $condition);
                }
            }
            $this->success($msg . ' 成功');
        } else {
            $this->error($msg . ' 错误');
        }
    }

    protected function modelCreate($model, $data, $validate = '', $msg = '添加', \Closure $callback = null)
    {
        if ($validate) {
            $this->handleValidate($data, $validate);
        }
        $res = model($model)->allowField(true)->create($data);
        if (false == $res) {
            $this->error(model($model)->getError());
        } elseif ($res) {
            $this->makeLog("[" . $msg . "成功] [MODEL] " . $model);
            if ($callback) {
                if (is_callable($callback)) {
                    $callback($res);
                }
            }
            $this->success($msg . '成功');
        } else {
            $this->error($msg . '失败');
        }
    }
//    public function modelInsert($model, $data, $validate = '', $callback = null)
//    {
//        if($validate) {
//            $this->handleValidate($data,$validate);
//        }
//        if(isset($data['__token__'])) unset($data['__token__']);
//        if(isset($data['file'])) unset($data['file']);
//        if(isset($data['id'])) unset($data['id']);
//        $res = model($model)->allowField(true)->create($data);
//        $msg = '新增';
//        if (false == $res) {
//            $this->error(model($model)->getError());
//        } elseif ($res) {
//            $this->makeLog("[".$msg."成功] [MODEL] " . $model);
//
//            dump($res);die;
//            if(is_callable($callback)) {
//                $callback($res);
//            }
//
//            $this->success($msg . '成功');
//        } else {
//            $this->error($msg . '失败');
//        }
//    }
    /*
    * name：moSave 新增或修改函数
    * param：模型，要添加的数据，（修改条件），success跳转路径，验证类名（默认关闭）
    * author：Ray
    */
//    public function moSave($model, $data, $condition = [], $validate = '', $path = "")
//    {
//        if($validate) {
//            $this->handleValidate($data,$validate);
//        }
//        if (!empty($condition)) {
////            unset($condition['id']);
//            $res = model($model)->allowField(true)->save($data, $condition);
//            $msg = '修改';
//        } else {
//            $res = model($model)->allowField(true)->save($data);
//            $msg = '新增';
//        }
//
//        if (false === $res) {
//            $this->error(model($model)->getError());
//        } elseif ($res === 0) {
//            $this->error('无' . $msg);
//        } elseif ($res) {
//            if (!empty($condition)) $this->makeLog("[新增成功] [MODEL] " . $model);
//            return $path ? $this->success($msg . '成功', $path) : $this->success($msg . '成功');
//        } else {
//            $this->error($msg . '失败');
//        }
//    }

    /*
    * name：dbUpdate数据更新方法
    */
    protected function dbUpdate($db, $data, $condition, $path = "")
    {
        $res = db($db)->where($condition)->update($data);
        if ($res) $this->makeLog('[更新成功] [DB] ' . $db . ' [' . key($condition) . '] ' . current($condition));
        $res ? $this->success('更新成功', $path) : $this->error('更新失败', $path);
    }

    /*
    * name：moDelete数据删除方法
    * param：模型，删除条件
    * author：Ray
    */
    protected function modelDelete($model, $condition)
    {
        $res = model($model)->where($condition)->delete();
        if ($res) $this->makeLog('[删除成功] [MODEL] ' . $model);
        echo $res ? 1 : 0;
    }

    //数据库的删除方法
    protected function dbDelete($db, $condition)
    {
        $res = db($db)->where($condition)->delete();
        if ($res) $this->makeLog('[删除成功] [DB] ' . $db . ' [' . key($condition) . '] ' . current($condition));
        echo $res ? 1 : 0;
    }

    protected function fetchFormPageHtml($class, $form_action, $data = [], $makeFromDataAction = 'makeFromData', $pk = 'id')
    {
        $class = model($class);
        if (empty($data) && $id = input($pk)) {
            $data = $class->where($pk, $id)->find()->toArray();
        }
        $this->assign('data', $class->$makeFromDataAction($data));
        $this->assign('action', $form_action);
        return $this->fetch('public/form_builder');
    }

    protected function checkIsPost()
    {
        if (request()->isPost() == false) $this->error('非法请求');
    }

}